package gbench.sandbox.zk.junit;

import static gbench.common.matlib.MatlibCanvas.println;
import static gbench.common.tree.LittleTree.Term.FT;

import java.util.stream.Collectors;

import org.apache.curator.framework.recipes.cache.CuratorCache;
import org.apache.curator.framework.recipes.cache.CuratorCacheListener;
import org.junit.jupiter.api.Test;

import gbench.common.fs.XlsFile.SimpleExcel;
import gbench.common.matlib.data.DataReader.DFrame;
import gbench.common.tree.LittleTree.Json;
import gbench.common.tree.LittleTree.Term;
import gbench.sandbox.zk.zoo.ZKApp;
import gbench.sandbox.zk.zoo.ZKNode;
import gbench.sandbox.zk.zoo.ZKYmlEngine;

class JunitZk {

    @Test
    public void foo() {
        final var basehome = "F:\\slicef\\desktop\\doc\\s";
        final var excel = SimpleExcel.of(FT("$0\\zookeeper.xlsx", basehome));
        final var dfm = excel.autoDetect(0).collect(DFrame.dfmclc2);
        final var engine = new ZKYmlEngine().setRootName("/zhizhe"); // 注意
        final var tree = engine.yml(dfm);
        println(dfm);
        final var zkApp = new ZKApp("localhost:2181,localhost:2182,localhost:2183");
        zkApp.withTransaction(client -> {

            final var children = client.get_children_throws("/");
            println(children);

            client.get_tree_throws().forEach(node -> {
                final var line = Term.FT("$0$1$2", " | ".repeat(node.getLevel()), node.getName(),
                        node.getAttributes().toMap());
                println(line);
            }); // forEach
        }); // withClient

        zkApp.withTransaction(sess -> {

            final var g_path = "/zhizhe/中国";
            sess.addWatcher(g_path, event -> {
                final var _path = event.getPath();
                println("--watcher->", event.getState(), sess.recordOf(_path).i4("value"));
                System.out.println("监听到的变化 watchedEvent = " + event);
            }); // addWatcher

            final var client = sess.self();
            final var cache = CuratorCache.build(client, g_path);
            final var listener = CuratorCacheListener.builder().forCreates(node -> {
                System.err.println(FT("Node created. \n[$0]", new ZKNode(node)));
            }).forChanges((oldNode, node) -> {
                System.err.println(FT("Node changed. \nOld: [$0] \nNew: [$1]", new ZKNode(oldNode), new ZKNode(node)));
            }).forDeletes(oldNode -> {
                System.err.println(FT("Node deleted. \nOld value: [$0]", new ZKNode(oldNode)));
            }).forInitialized(() -> {
                System.err.println("Cache initialized");
            }).build();
            cache.listenable().addListener(listener); // 添加监听器
            cache.start();

            final var exists = sess.self().checkExists();
            final var nodes = tree.stream().collect(Collectors.toList());
            for (var e : nodes) {
                final var path = e.path();
                final var stat = exists.forPath(path);
                if (stat != null) {
                    println(path, stat.getDataLength());
                    println(path, new String(sess.self().getData().forPath(path)));
                    final var bb = sess.self().getData().forPath(path);
                    final var b = Json.json2rec(new String(bb));
                    b.compute("value", (Integer v) -> v == null ? 1 : v + 1);
                    sess.self().setData().forPath(path, b.json().getBytes());
                } else { // 数据创建
                    sess.create_persistent(path, e.attrs().derive("value", 1));
                } // if
            } // for
        });
    }

}